package com.dubbo.service.impl;

import com.dubbo.service.HelloService;
import org.apache.dubbo.common.threadpool.ThreadPool;
import org.apache.dubbo.config.annotation.Service;

import java.util.concurrent.ThreadLocalRandom;

/**
 * @author: wudong
 * @create: 2022-02-15 18:28
 **/
@Service
public class HelloServiceImpl implements HelloService {
    @Override
    public String methodA() {
        int sleep = sleep();
        return "methodA sleep " + sleep;
    }

    @Override
    public String methodB() {
        int sleep = sleep();
        return "methodB sleep " + sleep;
    }

    @Override
    public String methodC() {
        int sleep = sleep();
        return "methodC sleep " + sleep;
    }

    private int sleep(){
        int sleep = 0;
        int random = ThreadLocalRandom.current().nextInt(10);
        if(random < 3){
            sleep = getRandomVariable(300);
        }else {
            sleep = getPossionVariable(80);
        }
        try {
            Thread.sleep(sleep);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return sleep;
    }

    private static int getRandomVariable(int bound){
        return ThreadLocalRandom.current().nextInt(bound);
    }

    private static int getPossionVariable(double lamda) {
        int x = 0;
        double y = Math.random(), cdf = getPossionProbability(x, lamda);
        while (cdf < y) {
            x++;
            cdf += getPossionProbability(x, lamda);
        }
        return x;
    }

    private static double getPossionProbability(int k, double lamda) {
        double c = Math.exp(-lamda), sum = 1;
        for (int i = 1; i <= k; i++) {
            sum *= lamda / i;
        }
        return sum * c;
    }
}
